package com.biz.primus.ms.member.service;

import com.biz.primus.base.exception.BizBusinessException;
import com.biz.primus.base.exception.BizParameterException;
import com.biz.primus.model.member.exception.UserException;
import com.biz.primus.model.member.exception.UserExceptionType;
import com.biz.primus.model.member.vo.MemberBankCardVo;
import com.biz.primus.ms.base.service.AbstractBaseService;
import com.biz.primus.ms.member.dao.po.MemberBankCard;
import com.biz.primus.ms.member.dao.redis.MemberBankCardRedisDao;
import com.biz.primus.ms.member.dao.repository.MemberBankCardRepository;
import com.biz.primus.ms.member.dao.ro.MemberBankCardRo;
import com.biz.primus.ms.member.dao.ro.MemberRo;
import com.biz.primus.ms.member.trans.MemberBankCardRoToMemberBankCardVo;
import com.biz.primus.ms.member.trans.MemberBankCardToMemberBankCardRo;
import com.google.common.collect.Lists;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.sql.Timestamp;
import java.util.List;

/**
 * 银行卡
 * @author jun.liu
 * @date 2017年10月23日
 * @reviewer
 * @see
 */
@Slf4j
@Service
public class MemberBankCardService extends AbstractBaseService
{
    private final MemberBankCardRedisDao memberBankCardRedisDao;

    private final MemberBankCardRepository memberBankCardRepository;

    private final MemberService memberService;

    @Autowired
    public MemberBankCardService(MemberBankCardRedisDao memberBankCardRedisDao, MemberBankCardRepository memberBankCardRepository,
                                 MemberService memberService)
    {
        this.memberBankCardRedisDao = memberBankCardRedisDao;
        this.memberBankCardRepository = memberBankCardRepository;
        this.memberService = memberService;
    }

    /**
     * 保存或者修改银行卡信息 默认进来的为最后一次访问的银行卡
     * @param vo
     */
    @Transactional(rollbackFor = Exception.class)
    public void save(MemberBankCardVo vo)
    {
        if (vo == null)
        {
            throw new UserException(UserExceptionType.PARAMS_ERROR);
        }
        if (vo.getMemberId() == null)
        {
            throw new UserException(UserExceptionType.MEMBERID_NULL);
        }
        //服务中已经验证了空值和空对象 无须在进行判断
        MemberRo memberRo = this.memberService.findRoById(vo.getMemberId());
        List<MemberBankCard> pos = memberBankCardRepository.findByMemberId(memberRo.getId());
        List<MemberBankCard> savePos = Lists.newArrayList();
        if (vo.getId() != null && vo.getId() != 0L) {
            if (pos != null && !pos.isEmpty())
            {
                for (MemberBankCard po : pos)
                {
                    if (vo.getId().longValue() == po.getId().longValue())
                    {
                        po.setLastUse(true);
                        po.setUpdateTimestamp(new Timestamp(System.currentTimeMillis()));
                        savePos.add(po);
                    }
                    else
                    {
                        if (po.getLastUse())
                        {
                            po.setLastUse(false);
                            savePos.add(po);
                        }
                    }
                }
            }
        }
        else
        {
            MemberBankCard po = new MemberBankCard();
            BeanUtils.copyProperties(vo, po);
            po.setMemberId(memberRo.getId());
            savePos.add(po);
        }
        batchSaveOrUpdateUsingPoPKIncreament(memberBankCardRepository, memberBankCardRedisDao, savePos, new MemberBankCardToMemberBankCardRo());
    }

    /**
     * 根据id获取po
     * @param id
     * @return
     */
    public MemberBankCard findPoById(Long id) {
        if (id == null || id == 0L) {
            throw new BizParameterException("id Parameter is null");
        }
        MemberBankCard po = memberBankCardRepository.findOne(id);
        if (po == null) {
            throw new BizBusinessException("MemberBankCard result is null");
        }
        return po;
    }

    /**
     * 根据id获取ro
     * @param id
     * @return
     */
    public MemberBankCardRo findRoById(Long id) {
        if (id == null || id == 0L) {
            throw  new UserException(UserExceptionType.BANK_CARD_ID_NULL);
        }
        MemberBankCardRo ro = memberBankCardRedisDao.findOne(id);
        if (ro == null) {
            throw new UserException(UserExceptionType.BANK_CARD_NULL);
        }
        return ro;
    }

    /**
     * 根据id获取vo
     * @param id
     * @return
     */
    public MemberBankCardVo findVoById(Long id) {
        return new MemberBankCardRoToMemberBankCardVo().apply(findRoById(id));
    }

    /**
     * 根据memberId获取vo
     * @param memberId
     * @return
     */
    public MemberBankCardVo findVoByMemberIdOnLastUse(Long memberId) {
        MemberBankCard po = memberBankCardRepository.findByMemberIdAndLastUse(memberId, true);
        if (po == null) {
            List<MemberBankCard> pos = memberBankCardRepository.findByMemberId(memberId);
            if(pos != null && !pos.isEmpty())
            {
                po = pos.get(0);
                po.setLastUse(true);
                saveOrUpdateUsingPoPKIncreament(memberBankCardRepository, memberBankCardRedisDao, po, new MemberBankCardToMemberBankCardRo());
            }
        }
        MemberBankCardVo vo = new MemberBankCardVo();
        if (po != null)
        {
            BeanUtils.copyProperties(po, vo);
        }
        return vo;
    }
}
